/*
 * Copyright (c) 2015. For Intelligent Group.
 */

package com.intelligent.ispc.common.mapper;

import org.springframework.beans.BeanUtils;
import org.springframework.beans.BeanWrapper;
import org.springframework.beans.BeanWrapperImpl;

import java.lang.reflect.Method;
import java.util.HashSet;
import java.util.Set;

/**
 * Created by cherry on 2015/12/9.
 */
public class BeanUtil extends BeanUtils {

    private static String[] getNullPropertyNames(Object source) {
        final BeanWrapper src = new BeanWrapperImpl(source);
        java.beans.PropertyDescriptor[] pds = src.getPropertyDescriptors();

        Set<String> emptyNames = new HashSet<String>();
        for (java.beans.PropertyDescriptor pd : pds) {
            Object srcValue = src.getPropertyValue(pd.getName());
            if (srcValue == null) {
                emptyNames.add(pd.getName());
            }
        }
        String[] result = new String[emptyNames.size()];
        return emptyNames.toArray(result);
    }

    // then use Spring BeanUtils to copy and ignore null
    public static void copyBeanPropertiesWithoutNull(final Object source, final Object target) {
        BeanUtils.copyProperties(source, target, getNullPropertyNames(source));
    }

    public static Object CopyBeanToBean(Object obj1, Object obj2) throws Exception {
        Method[] method1 = obj1.getClass().getMethods();
        Method[] method2 = obj2.getClass().getMethods();
        String methodName1;
        String methodFix1;
        String methodName2;
        String methodFix2;
        for (int i = 0; i < method1.length; i++) {
            methodName1 = method1[i].getName();
            methodFix1 = methodName1.substring(3, methodName1.length());
            if (methodName1.startsWith("get")) {
                Object[] objs1 = new Object[0];
                Object[] objs2 = new Object[1];
                objs2[0] = method1[i].invoke(obj1, objs1);
                if (objs2[0] != null) {
                    for (int j = 0; j < method2.length; j++) {
                        methodName2 = method2[j].getName();
                        methodFix2 = methodName2.substring(3, methodName2.length());
                        if (methodName2.startsWith("set")) {
                            if (methodFix2.equals(methodFix1)) {
                                Object[] objs11 = new Object[0];
                                Object[] objs12 = new Object[1];
                                objs12[0] = method1[i].invoke(obj1, objs11);
                                method2[j].invoke(obj2, objs12);
                                continue;
                            }
                        }
                    }
                }
            }
        }
        return obj2;

    }
}

